unit uTypesGraph;

{$mode objfpc}{$H+}

interface

uses
    Classes, SysUtils, contnrs;

type
    TFPGraphNode = class;
    TFPGraphEdge = class;
    TFPGraphEdges = class;
    TFPGraph = class;

    { TFPGraphElement }

    TFPGraphElement = class
    private
        FData: Pointer;
        procedure SetData(AValue: Pointer);
    protected
        procedure Init; virtual;
        procedure Done; virtual;

        function PropsCount: Integer; virtual;
        function PropAsString(const aPropIndex: Integer): string; virtual;

    public
        constructor Create;
        destructor Destroy; virtual;
        property Data: Pointer read FData write SetData;
    end;

    { TFPGraphNode }

    TFPGraphNode = class(TFPGraphElement)

    end;

    TFPGraphNodeClass = class of TFPGraphNode;

    { TFPGraphEdge }

    TFPGraphEdge = class(TFPGraphElement)
    private
        FNodeFrom: TFPGraphNode;
        FNodeTo: TFPGraphNode;
        procedure SetNodeFrom(AValue: TFPGraphNode);
        procedure SetNodeTo(AValue: TFPGraphNode);
    protected
    public
        property NodeFrom: TFPGraphNode read FNodeFrom write SetNodeFrom;
        property NodeTo: TFPGraphNode read FNodeTo write SetNodeTo;
    end;

    TFPGraphEdgeClass = class of TFPGraphEdge;

    { TFPGraphNodes }

    TFPGraphNodes = class
    private
        FItems: TFPList;
        FNodeClass: TFPGraphNodeClass;
        function GetInternalItems(aIndex: Integer): TFPGraphNode;
        procedure SetInternalItems(aIndex: Integer; AValue: TFPGraphNode);
    protected
        function InternalAddNew: TFPGraphNode;
        property InternalItems[aIndex: Integer]: TFPGraphNode read GetInternalItems write SetInternalItems;
    public
        function Count: Cardinal; inline;
    end;

    { TFPGraphEdges }

    TFPGraphEdges = class
    private
        FItems: TFPList;
        FEdgeClass: TFPGraphEdgeClass;
        function GetInternalItems(aIndex: Integer): TFPGraphEdge;
        procedure SetInternalItems(aIndex: Integer; AValue: TFPGraphEdge);
    protected
        function InternalAddNew: TFPGraphEdge;
        property InternalItems[aIndex: Integer]: TFPGraphEdge read GetInternalItems write SetInternalItems;
    public
        function Count: Cardinal; inline;
    end;

    TFPGraph = class

    end;


implementation

{ TFPGraphNodes }

function TFPGraphNodes.GetInternalItems(aIndex: Integer): TFPGraphNode;
begin

end;

procedure TFPGraphNodes.SetInternalItems(aIndex: Integer; AValue: TFPGraphNode);
begin

end;

function TFPGraphNodes.InternalAddNew: TFPGraphNode;
begin

end;

function TFPGraphNodes.Count: Cardinal;
begin

end;

{ TFPGraphEdges }

function TFPGraphEdges.GetInternalItems(aIndex: Integer): TFPGraphEdge;
begin
    Result := TFPGraphEdge(FItems[aIndex]);
end;

procedure TFPGraphEdges.SetInternalItems(aIndex: Integer; AValue: TFPGraphEdge);
begin
    FItems[aIndex] := AValue;
end;

function TFPGraphEdges.InternalAddNew: TFPGraphEdge;
begin
    Result := FEdgeClass.Create;
    FItems.Add(Result);
end;

function TFPGraphEdges.Count: Cardinal;
begin
    Result := FItems.Count;
end;

{ TFPGraphElement }

procedure TFPGraphElement.SetData(AValue: Pointer);
begin
    if FData = AValue then
        Exit;
    FData := AValue;
end;

procedure TFPGraphElement.Init;
begin
    Data := nil;
end;

procedure TFPGraphElement.Done;
begin

end;

function TFPGraphElement.PropsCount: Integer;
begin
    Result := 0;
end;

function TFPGraphElement.PropAsString(const aPropIndex: Integer): string;
begin
    Result := '';
end;

constructor TFPGraphElement.Create;
begin
    Init;
end;

destructor TFPGraphElement.Destroy;
begin
    Done;
end;

{ TFPGraphEdge }

procedure TFPGraphEdge.SetNodeFrom(AValue: TFPGraphNode);
begin
    if FNodeFrom = AValue then
        Exit;
    FNodeFrom := AValue;
end;

procedure TFPGraphEdge.SetNodeTo(AValue: TFPGraphNode);
begin
    if FNodeTo = AValue then
        Exit;
    FNodeTo := AValue;
end;

end.
